// Author: Ivan Kazmenko (gassa@mail.ru)
// Generator for problem "worm"
module gen;
import std.algorithm;
import std.conv;
import std.exception;
import std.format;
import std.math;
import std.random;
import std.range;
import std.stdio;

immutable string testFormat = "%03d";
enum generateAnswers = false;

immutable int maxC = 10 ^^ 9;

struct Point
{
	int x;
	int y;

	bool isValid () const
	{
		return abs (x) <= maxC && abs (y) <= maxC;
	}

	string toString () const
	{
		return format ("%s %s", x, y);
	}
}

struct Test
{
	Point a;
	Point b;

	string comment;

	void validate () const
	{
		enforce (a.isValid ());
		enforce (b.isValid ());
	}

	void print (File f) const
	{
		f.writeln (a);
		f.writeln (b);
	}

	string log () const
	{
		return format ("%s (%s, %s)", comment, a, b);
	}
}

Test [] tests;

void printAllTests ()
{
	foreach (testNumber, test; tests)
	{
		test.validate ();
		auto testString = format (testFormat, testNumber + 1);
		auto f = File (testString, "wt");
		test.print (f);
		static if (generateAnswers)
		{
			auto g = File (testString ~ ".a", "wt");
			test.printAnswer (g);
		}
		writeln (testString, ": ", test.log ());
	}
}

Mt19937 rndLocal;

void main ()
{
	rndLocal.seed (157_159_006);

	tests ~= Test (Point (-1, -1), Point (3, 0), "example test 1");
	tests ~= Test (Point (-1, -1), Point (0, 3), "example test 2");

	tests ~= Test (Point (0, 0), Point (-1, 0), "minimal test 1");
	tests ~= Test (Point (-1, -1), Point (0, -1), "minimal test 2");

	tests ~= Test (Point (10, 15), Point (15, 10), "medium test 1");
	tests ~= Test (Point (-23, 48), Point (71, 16), "medium test 2");
	tests ~= Test (Point (-55, 56), Point (-91, 54), "medium test 3");
	tests ~= Test (Point (-55, -128), Point (81, 33), "medium test 4");

	tests ~= Test (Point (1000000000, -12345),
	    Point (-999999999, 23456), "maximal test 1");
	tests ~= Test (Point (12345678, 999999999),
	    Point (-12384567, -999999999), "maximal test 2");
	tests ~= Test (Point (-1000000000, 1000000000),
	    Point (1000000000, -1000000000), "maximal test 3");
	tests ~= Test (Point (1000000000, 987654321),
	    Point (-1000000000, 123456789), "maximal test 4");

	printAllTests ();
}
